const fs = require('fs');
const merge = require('merge');
const path = require('path');
const webpack = require('webpack');
const { getDirectories, getResolvePathFn } = require('./build/util');
const BuildConfigWebpackPlugin = require('build-config-webpack-plugin');

const resolvePath = getResolvePathFn(__dirname);
const isDev = process.env.NODE_ENV === 'development';

// get modules
const modulesPath = './src/modules';
const modules = getDirectories(resolvePath(modulesPath));
const pagesConfigs = {};

const extensions = ['.tsx', '.jsx', '.js', '.ts', '.vue'];

// loop pages and config entry
modules.forEach(module => {
  const chunk = module.toLowerCase();
  const templateFile = 'index.html';
  const outputFile = `${chunk}.html`;
  const pagePath = `${modulesPath}/${module}`;

  // get entry file
  let entry = '';
  for (const ext of extensions) {
    entry = resolvePath(`${pagePath}/main${ext}`);
    try {
      if (fs.existsSync(entry)) {
        break;
      }
    } catch (err) {
      console.error(err);
    }
  }

  const pageConfig = {
    // entry for the page
    entry,
    // the html template
    template: resolvePath(`${pagePath}/${templateFile}`),
    // output as dist/module.html
    filename: outputFile,
    // chunks to include on this page, by default includes
    // extracted common chunks and vendor chunks.
    chunks: ['chunk-vendors', 'chunk-common', chunk]
  };

  pagesConfigs[chunk] = pageConfig;
});

module.exports = {
  productionSourceMap: isDev,
  publicPath: process.env.VUE_APP_PUBLIC_PATH,
  devServer: {
    hot: true,
    port: process.env.VUE_APP_DEV_PORT,
    headers: {
      'Access-Control-Allow-Origin': '*'
    },
    contentBase: [resolvePath('dist'), resolvePath('node_modules/vendor/dist')]
  },
  css: {
    loaderOptions: {
      less: {
        lessOptions: {
          javascriptEnabled: true
        }
      }
    }
  },
  pages: pagesConfigs,
  configureWebpack: config => {
    config.output.filename = '[name].[hash].js';

    if (!isDev) {
      config.plugins.push(
        new webpack.DllReferencePlugin({
          manifest: require('vendor/dist/vendor-manifest.json')
        })
      );
    }

    const customConfig = {};
    config.resolve.extensions = extensions;

    if (!isDev) {
      // add custom plugins
      config.plugins.push(new BuildConfigWebpackPlugin());

      customConfig.devtool = 'none';
    } else {
      if (process.env.VUE_APP_CURD_TABLE_PATH) {
        const alias = config.resolve.alias || {};
        const CURD_TABLE_PATH = process.env.VUE_APP_CURD_TABLE_PATH.replace(
          '/',
          path.sep
        );
        alias['curd-table'] = path.resolve(
          __dirname,
          `${CURD_TABLE_PATH}/src/index.js`
        );
      }
      customConfig.devtool = 'source-map';
    }

    merge(config, customConfig);
  },
  chainWebpack(config) {
    // ts loader
    config.module
      .rule('typescript')
      .test(/\.ts(x?)$/)
      .use('ts-loader')
      .loader('ts-loader')
      .end();
  }
};
